package com.zhou.cloud.controller;

import com.alibaba.csp.sentinel.annotation.SentinelResource;
import com.alibaba.fastjson.JSONObject;
import com.zhou.cloud.dao.entity.Order;
import com.zhou.cloud.entry.DemoHttpClient;
import com.zhou.cloud.entry.DemoHttpConst;
import com.zhou.cloud.entry.DemoHttpRespStatus;
import com.zhou.cloud.service.IOrderService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.http.*;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.bind.annotation.*;

import java.text.MessageFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @author zhouyongjun
 * @Description:
 * @date 2021/4/6 16:45
 */
@RestController
@RequestMapping("order")
@Slf4j
public class OrderController {
    @Autowired
    IOrderService orderService;
    //商品服务客户端访问封装对象
    @Autowired
    @Qualifier("productHttpClient")
    DemoHttpClient productHttpClient;
   //uuid生成访问客户端
    @Autowired
    @Qualifier("uuidHttpClient")
    DemoHttpClient uuidHttpClient;
    @GetMapping("/get/{id}")
    public Order get(@PathVariable("id") Long id) {
        Order order = orderService.get(id);
        System.out.println(order);
        return order;
    }

    @PostMapping("/add")
    @SentinelResource(value = "order-add",fallback = "optFailBack",blockHandler = "optFailBack")
    public JSONObject add(Order order) throws Exception {
        Long uuid =  generatorUuid();
//        sold(order.getProductId(),order.getBuyNum());
        soldCache(order.getProductId(),order.getBuyNum());
        order.setUuid(uuid);
        order.setCreateTime(System.currentTimeMillis());
        boolean isTrue = orderService.add(order);
        JSONObject result = new JSONObject();
        if(isTrue)
        {
            result.put(DemoHttpConst.RESP_CODE, DemoHttpRespStatus.OK);
        }else
        {
            result.put(DemoHttpConst.RESP_CODE, DemoHttpRespStatus.FAIL);
            result.put(DemoHttpConst.RESP_MSG, "订单创建失败");
        }

        return result;
    }

    private void soldCache(Long productId, Integer buyNum) throws Exception {
        String url = MessageFormat.format("{0}product/sold/cache/{1}",productHttpClient.getUrl(),productId);
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        MultiValueMap<String,Object> requestMap = new LinkedMultiValueMap<>();
        requestMap.add("delNum",String.valueOf(buyNum));
        HttpEntity<MultiValueMap<String,Object>> requestEntity = new HttpEntity<>(requestMap);
        ResponseEntity<JSONObject> responseEntity = productHttpClient.getRestTemplate().exchange(url,HttpMethod.PUT,requestEntity,JSONObject.class);
        JSONObject responseBody = responseEntity.getBody();
        if(!DemoHttpRespStatus.OK.name().equals(responseBody.getString("code")))
        {
            throw new Exception();
        }
    }

    private void sold(Long productId,int num) throws Exception {
        String url = MessageFormat.format("{0}product/sold/{1}",productHttpClient.getUrl(),productId);
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        MultiValueMap<String,Object> requestMap = new LinkedMultiValueMap<>();
        requestMap.add("delNum",String.valueOf(num));
        HttpEntity<MultiValueMap<String,Object>> requestEntity = new HttpEntity<>(requestMap);
        ResponseEntity<JSONObject> responseEntity = productHttpClient.getRestTemplate().exchange(url,HttpMethod.PUT,requestEntity,JSONObject.class);
        JSONObject responseBody = responseEntity.getBody();
        if(!DemoHttpRespStatus.OK.name().equals(responseBody.getString("code")))
        {
            throw new Exception();
        }
    }

    private Long generatorUuid() {
        String url = MessageFormat.format("{0}uuid/generator",uuidHttpClient.getUrl());
        ResponseEntity<JSONObject> uuidResponseEntity = uuidHttpClient.getRestTemplate().getForEntity(url,JSONObject.class);
        JSONObject uuidRespJSON = uuidResponseEntity.getBody();
        return uuidRespJSON.getLong(DemoHttpConst.RESP_UUID);
    }

    @DeleteMapping("del/{id}")
    public boolean delete(@PathVariable("id") Long id) {
        return false;
    }

    @GetMapping("/list")
    @SentinelResource(value = "order-list",fallback = "listFallback",blockHandler = "listFallback")
    public List<Order> list() {
        List<Order> list = orderService.getAll();
        System.out.println(list);
        return list;
    }
    @GetMapping("/list/page")
    @SentinelResource(value = "provider-list",fallback = "listFallback",blockHandler = "listFallback")
    public List<Order> pageList(int page,int pageNum) {
        List<Order> list = orderService.getListByPage(page,pageNum);
        System.out.println(list);
        return list;
    }
    public List<Order> listFallback(Throwable e){
        if (e != null){
            log.error("",e);
        }

        String msg = "listfallback ...";
        log.warn("<<<<fallback");
        return new ArrayList<>();
    }

    public JSONObject optFailBack(Throwable e) {
        JSONObject jsonObject = new JSONObject();
        jsonObject.put(DemoHttpConst.RESP_CODE,DemoHttpRespStatus.FAIL);
        jsonObject.put(DemoHttpConst.RESP_MSG,"操作异常");
        log.error("",e);
        return jsonObject;
    }

}
